#include <spdlog/logger.h>
#include <spdlog/sinks/stdout_color_sinks.h>
#include <spdlog/sinks/basic_file_sink.h>
#include <spdlog/async.h>
#include <string>


namespace myChatSystem
{
    // 创建一个全局的日志
    std::shared_ptr<spdlog::logger> g_defult_logger;
    
    //  @mode 运行模式      true 发布模式 false 调试模式
    //  @filename 要输出的文件名
    //  @level 日志等级
    void init_logger(bool mode ,const std::string &filename,size_t level)
    {
        if(!mode)
        {
            //如果是调试模式，则创建标准输出日志器，输出等级为最低
            g_defult_logger =spdlog::stdout_color_mt("defult_logger");
            g_defult_logger->set_level(spdlog::level::level_enum::trace);       // 设置日志等级
            g_defult_logger->flush_on(spdlog::level::level_enum::trace);        //触发刷新条件：当日志记录的级别等于或高于 flush_on 设置的级别时，spdlog 会自动将缓冲区中的日志内容写入目标。
        }
        else
        {
            //否则是发布模式，则创建文件输出日志器，输出等级根据参数而定
            g_defult_logger = spdlog::basic_logger_mt("defult_logger",filename);
            g_defult_logger->set_level((spdlog::level::level_enum)level);
            g_defult_logger->flush_on((spdlog::level::level_enum)level);
        }
        /*
            设置日志输出格式
            [%n]：logger 名称    
            [%H:%M:%S]：时间戳   
            [%t]：线程 ID
            [%-8l]：日志级别    %l：日志级别（如 TRACE, DEBUG, INFO 等）。  （%-8：格式修饰符：-：左对齐。8：固定占 8 个字符宽度，不足时用空格填充。）
            %v：实际日志消息        %v 表示用户调用日志时传入的文本内容。示例：logger->info("Hello World"); 会输出 Hello World。
        */
        g_defult_logger->set_pattern("[%N][%H:%M:%S][%t][%-8l]%v");
    }
}
/*
    [{}:{}] "：固定前缀，包含两个占位符 {}，分别对应文件名 __FILE__ 和行号 __LINE__。
    ##__VA_ARGS__       作用：处理可变参数（Variadic Arguments），确保宏在无额外参数时语法正确。
    场景：  (1)当用户调用时没有额外参数，##__VA_ARGS__ 会消除前面的逗号，避免语法错误。  (2)当用户调用时有额外参数，##__VA_ARGS__ 会展开为这些参数。
*/
#define LOG_TRACE(format,...)   myChatSystem::g_defult_logger->trace(std::string("[{}:{}] ")+format,__FILE__,__LINE__,##__VA_ARGS__);
#define LOG_DEBUG(format,...)   myChatSystem::g_defult_logger->debug(std::string("[{}:{}] ")+format,__FILE__,__LINE__,##__VA_ARGS__);
#define LOG_INFO(format,...)    myChatSystem::g_defult_logger->info(std::string("[{}:{}] ")+format,__FILE__,__LINE__,##__VA_ARGS__);
#define LOG_WARN(format,...)    myChatSystem::g_defult_logger->warn(std::string("[{}:{}] ")+format,__FILE__,__LINE__,##__VA_ARGS__);
#define LOG_ERROR(format,...)   myChatSystem::g_defult_logger->error(std::string("[{}:{}] ")+format,__FILE__,__LINE__,##__VA_ARGS__);
#define LOG_FATAL(format,...)   myChatSystem::g_defult_logger->critical(std::string("[{}:{}] ")+format,__FILE__,__LINE__,##__VA_ARGS__);
